package com.example.concurrent;

import sun.misc.Unsafe;

import java.lang.reflect.Field;

public class Juc03_CAS {

    private volatile int count = 0;

    private static long offset;
    private static Unsafe unsafe;

    //通过反射初始化Unsafe魔法类
    static {
        try {
            Field f = Unsafe.class.getDeclaredField("theUnsafe");
            f.setAccessible(true);
            unsafe = (Unsafe) f.get(null);
            offset = unsafe.objectFieldOffset(Juc03_CAS.class.getDeclaredField("count"));
        } catch (NoSuchFieldException | IllegalAccessException e) {
            e.printStackTrace();
        }
    }

    //通过CAS来保证并发下的 count++ 的正确性
    public static void main(String[] args) throws InterruptedException {
        Juc03_CAS juc03_cas = new Juc03_CAS();
        for (int i = 0; i < 10; i++) {
            int finalI = i;
            Thread thread = new Thread(() -> {
                Thread.currentThread().setName("线程" + finalI + "： ");

                for (int j = 0; j < 1000; j++) {
                    juc03_cas.increment();
                }
            });
            thread.start();
        }
        Thread.sleep(2000);
        System.out.println("操作结束：" + juc03_cas.count);
    }


    private void increment() {
        // 失败了就重试直到成功为止
        int before = count;
        // 失败了就重试直到成功为止
        while (!unsafe.compareAndSwapInt(this, offset, before, before + 1)) {
            before = count;
        }
    }

    private int getCount(){
        return this.count;
    }
}
